﻿using System;
using System.Collections.Generic;
using System.Linq;
using System.Text;
using System.Data.Objects;

using Microsoft.Moles.Framework;
using Microsoft.Moles.Framework.Behaviors;

using Infraestructure.Data.Core;
using Infraestructure.Data.Core.Extensions;
using Entities = Domain.MainModule.Entities;

namespace Infraestructure.Data.MainModule.Mock
{
    /// <summary>
    /// Fake container for testing purposes.
    /// Implemented with Microsoft Moles and Stubs
    /// </summary>
    public class FakeMainModuleUnitOfWork
        : Infraestructure.Data.MainModule.UnitOfWork.Moles.SIMainModuleUnitOfWork
    {

        #region fields

        static List<Entities.Address> _Addresses;
        static List<Entities.AddressType> _AddressTypes;
        static List<Entities.BankAccount> _BankAccounts;
        static List<Entities.Branch> _Branches;
        static List<Entities.Country> _Countries;
        static List<Entities.City> _Cities;
        static List<Entities.Gender> _Genders;
        static List<Entities.MaritalStatus> _MaritalStatuses;
        static List<Entities.GroupBranch> _GroupBranches;
        static List<Entities.BillingInformation> _BillingInformations;
        static List<Entities.Identity> _Identities;
        static List<Entities.IdentityType> _IdentityTypes;
        static List<Entities.Order> _Orders;
        static List<Entities.Phone> _Phones;
        static List<Entities.PhoneType> _PhoneTypes;
        static List<Entities.SoundexCode> _SoundexCodes;
        static List<Entities.State> _States;
        static List<Entities.VirtualAccount> _VirtualAccounts;
        static List<Entities.CreditCard> _CreditCards;
        static List<Entities.CustomerService> _CustomerServices;
        static List<Entities.GroupBranchCurrency> _GroupBranchCurrencies;
        static List<Entities.OrderDetail> _OrderDetails;
        static List<Entities.RateParamType> _RateParamTypes;
        static List<Entities.Rate> _Rates;
        static List<Entities.RetailRate> _RetailRates;
        static List<Entities.User> _Users;
        static List<Entities.BankAccountType> _BankAccountTypes;
        static List<Entities.Bank> _Banks;

        #endregion

        #region constructor

        public FakeMainModuleUnitOfWork()
        {
            //Set default behavior for not stubbed elements ( DEFAULT BEHAVIOR THROW NOT IMPLEMENTED EXCEPTION)
            this.InstanceBehavior = BehavedBehaviors.DefaultValue;

            InitiateInnerCollection();
            InitiateFakeData();
        }

        #endregion

        #region Methods for configure Fake for testing

        private void InitiateInnerCollection()
        {
            //addresses
            if (_Addresses == null)
            {
                _Addresses = new List<Entities.Address>()
                {
                    new Entities.Address()
                    {
                        AddressId = Guid.Parse("ABCDF000-1234-5678-9000-1234567890AB"),
                        Street = "Calle 13",
                        AddressType = new Entities.AddressType()
                        {
                            Name = "AT",
                            TypeId = Guid.NewGuid(),
                            Addresses = new Domain.Core.Entities.TrackableCollection<Entities.Address>()
                        },
                        City = new Entities.City()
                        {
                            Name = "Balcarce",
                            CityId = Guid.NewGuid()
                        },
                        UserId = Guid.Parse("ABCDF000-1234-5678-9000-1234567890CD")
                    }
                };
            }

            //address types
            if (_AddressTypes == null)
            {
                _AddressTypes = new List<Entities.AddressType>()
                {
                    new Entities.AddressType()
                    {
                        Name = "AT",
                        TypeId = Guid.NewGuid(),
                        Addresses = new Domain.Core.Entities.TrackableCollection<Entities.Address>()
                    }
                };
            }

            //bank accounts
            if (_BankAccounts == null)
            {
                _BankAccounts = new List<Entities.BankAccount>()
                {
                    new Entities.BankAccount()
                    {
                        BankAccountId = Guid.Parse("ABCDF000-1234-5678-9000-1234567890EF"),
                        BankAccountNumber  = "1",
                        UserId = Guid.Parse("ABCDF000-1234-5678-9000-123456789000"),
                        IsEnabled = true
                    }
                };
            }

            //branches
            if (_Branches == null)
            {
                _Branches = new List<Entities.Branch>()
                {
                    new Entities.Branch()
                    {
                        BranchId = Guid.Parse("ABCDFABC-1234-5678-9000-1234567890EF"),
                        Name = "Branch Name 01",
                        GroupBranchId = Guid.Parse("012DFABC-1234-5678-9000-1234567890EF")
                    },
                    new Entities.Branch()
                    {
                        BranchId = Guid.Parse("ABCDFABC-5678-5678-9000-1234567890EF"),
                        Name = "Branch Name 02",
                        GroupBranchId = Guid.Parse("012DFABC-1234-5678-9000-1234567890EF"),
                    },
                    new Entities.Branch()
                    {
                        BranchId = Guid.Parse("ABCDFABC-9012-5678-9000-1234567890EF"),
                        Name = "Branch Name 03",
                        GroupBranchId = Guid.Parse("999DFABC-1234-5678-9000-1234567890EF")
                    }
                };
            }

            //cities
            if (_Cities == null)
            {
                _Cities = new List<Entities.City>()
                {
                    new Entities.City()
                    {
                        CityId = Guid.Parse("ABCDF000-1234-5678-9000-ABCD567890AB"),
                        Name = "balcarce"
                    },
                    new Entities.City()
                    {
                        CityId = Guid.Parse("ABCDF000-1234-5678-9000-EFAB567890AB"),
                        Name = "mar del plata"
                    },
                    new Entities.City()
                    {
                        CityId = Guid.Parse("ABCDF000-1234-5678-9000-CDAB567890AB"),
                        Name = "buenos aires"
                    }
                };
            }

            //genders
            if (_Genders == null)
            {
                _Genders = new List<Entities.Gender>() 
                {
                    new Entities.Gender()
                    {
                        Description = "Male"
                    },
                    new Entities.Gender()
                    {
                        Description = "Female"
                    }
                };
            }

            //marital statuses
            if (_MaritalStatuses == null)
            {
                _MaritalStatuses = new List<Entities.MaritalStatus>() 
                {
                    new Entities.MaritalStatus()
                    {
                        Description = "Married"
                    },
                    new Entities.MaritalStatus()
                    {
                        Description = "Single"
                    },
                    new Entities.MaritalStatus()
                    {
                        Description = "Widower"
                    }

                };
            }

            //countries
            if (_Countries == null)
            {
                _Countries = new List<Entities.Country>()
                {
                    new Entities.Country()
                    {
                        CountryId = Guid.Parse("ABCDF000-1234-5678-9123-EFAB567890AB"),
                        ISO3166_Alpha2 = "ISO Alpha 2",
                        ISO3166_Alpha3 = "ISO Alpha 3",
                        Name="Argentina",
                        IsEnabled = true
                    },
                    new Entities.Country()
                    {
                        CountryId = Guid.Parse("ABCDF000-1234-5678-9456-EFAB567890AB"),
                        ISO3166_Numeric = "ISO Numeric",
                        Name="Spain",
                        IsEnabled = true
                    }
                };
            }

            //group branches
            if (_GroupBranches == null)
            {
                _GroupBranches = new List<Entities.GroupBranch>()
                {
                    new Entities.GroupBranch()
                    {
                        GroupBranchId = Guid.Parse("ABCDF123-1234-5678-9123-EFAB567890AB"),
                        BillingInformations = new Domain.Core.Entities.TrackableCollection<Entities.BillingInformation>(),
                        Name="GP 01",
                        Priority = 100
                    },
                    new Entities.GroupBranch()
                    {
                        GroupBranchId = Guid.Parse("ABCDF456-1234-5678-9123-EFAB567890AB"),
                        BillingInformations = new Domain.Core.Entities.TrackableCollection<Entities.BillingInformation>(),
                        Name="GP 02",
                        Priority = 10
                    }
                };
            }

            //billing informations
            if (_BillingInformations == null)
            {
                _BillingInformations = new List<Entities.BillingInformation>()
                {
                    new Entities.BillingInformation()
                    {
                        BillingInformationId = Guid.Parse("ABCDF456-1234-1234-9123-EFAB567890AB"),
                        GroupBranchId = Guid.Parse("ABCDF123-1234-5678-9123-EFAB567890AB"), 
                        CompanyName = "HP"
                    },
                    new Entities.BillingInformation()
                    {
                        BillingInformationId = Guid.Parse("ABCDF456-1234-5678-9123-EFAB567890AB"),
                        CompanyName = "IBM"
                    }
                };
            }

            //identities
            if (_Identities == null)
            {
                _Identities = new List<Entities.Identity>()
                {
                    new Entities.Identity()
                    {
                        IdentityId = Guid.Parse("ABCDF456-1234-5678-1234-EFAB567890AB"),
                        Value = "Identity Value 01",
                        UserId = Guid.Parse("ABCDF456-1234-5678-5678-EFAB567890FF")
                    },
                    new Entities.Identity()
                    {
                        IdentityId = Guid.Parse("ABCDF456-1234-5678-5678-EFAB567890AB"),
                        Value = "Identity Value 02"
                    }
                };
            }

            //identity types
            if (_IdentityTypes == null)
            {
                _IdentityTypes = new List<Entities.IdentityType>()
                {
                    new Entities.IdentityType()
                    {
                        TypeId = Guid.Parse("ABCDF456-1234-5678-5678-CCCCCCCCCCCC"),
                        Name = "IT"
                    },
                    new Entities.IdentityType()
                    {
                        TypeId = Guid.Parse("ABCDF456-1234-5678-5678-DDDDDDDDDDDD"),
                        Name = "IT"
                    }
                };
            }

            //orders
            if (_Orders == null)
            {
                _Orders = new List<Entities.Order>()
                {
                    new Entities.Order()
                    {
                        OrderId= Guid.Parse("ABCDF456-1234-5678-5678-CCCCCCAAAAAA"),
                        ExtraInfo = "Extra 01"
                    },
                    new Entities.Order()
                    {
                        OrderId= Guid.Parse("ABCDF456-1234-5678-5678-CCCCCCBBBBBB"),
                        ExtraInfo = "Extra 01"
                    }
                };
            }

            //phone
            if (_Phones == null)
            {
                _Phones = new List<Entities.Phone>()
                {
                    new Entities.Phone()
                    {
                        PhoneId = Guid.Parse("ABCDF456-1234-5678-5678-AAAAAABBBBBB"),
                        Value = "Phone Value 01",
                        UserId =  Guid.Parse("01CDF456-1234-5678-5678-AAAAAABBBBBB")
                    },
                    new Entities.Phone()
                    {
                        PhoneId = Guid.Parse("ABCDF456-1234-5678-5678-FFFFFFBBBBBB"),
                        Value = "Phone Value 02",
                        UserId =  Guid.Parse("02CDF456-1234-5678-5678-AAAAAABBBBBB")
                    }
                };
            }

            //phone types
            if (_PhoneTypes == null)
            {
                _PhoneTypes = new List<Entities.PhoneType>()
                {
                    new Entities.PhoneType()
                    {
                        TypeId =  Guid.Parse("ABCDF456-1234-5678-5678-AAAACCBBBBBB"),
                        Name = "Home Phone"
                    },
                    new Entities.PhoneType()
                    {
                        TypeId =  Guid.Parse("ABCDF456-1234-5678-5678-AAAADDBBBBBB"),
                        Name = "Mobile Phone"
                    }
                };
            }

            //soundex codes
            if (_SoundexCodes == null)
            {
                _SoundexCodes = new List<Entities.SoundexCode>()
                {
                    new Entities.SoundexCode()
                    {
                        SoundexCodeId =  Guid.Parse("ABCDF456-1234-AAAA-5678-AAAACCBBBBBB"),
                        Value = "Soundex Code 01",
                        UserId = Guid.Parse("ABCDF456-CCCC-AAAA-BBBB-AAAACCBBBBBB"),
                        Code = "Code 01"
                    },
                    new Entities.SoundexCode()
                    {
                        SoundexCodeId =  Guid.Parse("ABCDF456-1234-BBBB-5678-AAAACCBBBBBB"),
                        Value = "Soundex Code 02",
                        UserId = Guid.Parse("ABCDF456-CCCC-AAAA-CCCC-AAAACCBBBBBB"),
                        Code = "Code 02"
                    }
                };
            }

            //states
            if (_States == null)
            {
                _States = new List<Entities.State>()
                {
                    new Entities.State()
                    {
                        StateId = Guid.Parse("ABCDF456-1234-BBBB-AAFF-AAAACCBBBBBB"),
                        Name = "state 01",
                        CountryId = Guid.Parse("ABCDF456-12CC-BBBB-AAFF-AAAACCBBBBBB")
                    },
                    new Entities.State()
                    {
                        StateId = Guid.Parse("ABCDF456-1234-BBBB-FFAA-AAAACCBBBBBB"),
                        Name = "state 02"
                    }
                };
            }

            //virtual accounts
            if (_VirtualAccounts == null)
            {
                _VirtualAccounts = new List<Entities.VirtualAccount>()
                {
                    new Entities.VirtualAccount()
                    {
                        VirtualAccountId = Guid.Parse("ABCDF456-1234-AABB-AAFF-AAAACCBBBBBB"),
                        IsEnabled = true,
                        Balance = 110
                    },
                    new Entities.VirtualAccount()
                    {
                        VirtualAccountId = Guid.Parse("ABCDF456-1234-AACC-AAFF-AAAACCBBBBBB"),
                        IsEnabled = true,
                        Balance = 10,
                        UserId = Guid.Parse("ABCDFAAA-1234-AACC-AAFF-AAAACCBBBBBB")
                    }
                };
            }
			
            //credit cards
            if (_CreditCards == null)
            {
                _CreditCards = new List<Entities.CreditCard>()
                {
                    new Entities.CreditCard()
                    {
                        CreditCardId = Guid.Parse("11111111-1234-AABB-AAFF-AAAACCBBBBBB"),
                        Number = "123456",
                        UserId = Guid.Parse("21111111-1234-AABB-AAFF-AAAACCBBBBBB") 
                    },
                    new Entities.CreditCard()
                    {
                        CreditCardId = Guid.Parse("11112222-1234-AABB-AAFF-AAAACCBBBBBB"),
                        Number = "777",
                        UserId = Guid.Parse("31111111-1234-AABB-AAFF-AAAACCBBBBBB") 
                    }
                };
            }
			
			//customer services
            if (_CustomerServices == null)
            {
                _CustomerServices = new List<Entities.CustomerService>()
                {
                    new Entities.CustomerService()
                    {
                        CustomerServiceId = Guid.Parse("ABCDF456-2222-AABB-AAFF-AAAACCBBBBBB"),
                        Description = "description 01",
                        OrderId = Guid.Parse("ABCDF456-1222-AABB-AAFF-AAAACCBBBBBB")
                    },
                    new Entities.CustomerService()
                    {
                        CustomerServiceId = Guid.Parse("ABCDF456-2233-AABB-AAFF-AAAACCBBBBBB"),
                        Description = "description 02",
                        OrderId = Guid.Parse("ABCDF456-3222-AABB-AAFF-AAAACCBBBBBB")
                    }
                };
            }
		
			//group branch services
            if (_GroupBranchCurrencies == null)
            {
                _GroupBranchCurrencies = new List<Entities.GroupBranchCurrency>()
                {
                    new Entities.GroupBranchCurrency()
                    {
                        GroupBranchCurrencyId = Guid.Parse("ABCDF456-1234-AABB-AAFF-123456BBBBBB"),
                        OperationType = new Entities.OperationType()
                        {
                            Name = "operation 01"
                        },
                        CurrencyId = Guid.Parse("ABCDF456-1234-AABB-AAFF-123456FBBBBB"),
                    },
                    new Entities.GroupBranchCurrency()
                    {
                        GroupBranchCurrencyId = Guid.Parse("ABCDF456-1234-AABB-AAFF-123456654321"),
                        OperationType = new Entities.OperationType()
                        {
                            Name = "operation 02"
                        },
                        CurrencyId = Guid.Parse("ABCDF456-1234-AABB-AAFF-123456DBBBBB")
                    }
                };
            }
			
			//order details
            if (_OrderDetails == null)
            {
                _OrderDetails = new List<Entities.OrderDetail>()
                {
                    new Entities.OrderDetail()
                    {
                        OrderDetailId = Guid.Parse("ABCDF456-1234-AABB-3333-AAAACCBBBBBB"),
                        Order = new Entities.Order()
                        {
                            ExtraInfo = "extra info 01"
                        },                        
                        OrderId = Guid.Parse("ABCDF456-1234-AABB-3333-AAAACCBBB123")
                    },
                    new Entities.OrderDetail()
                    {
                        OrderDetailId = Guid.Parse("ABCDF456-1234-AACC-4444-AAAACCBBBBBB"),
                        Order = new Entities.Order()
                        {
                            ExtraInfo = "extra info 02"
                        },
                        OrderId = Guid.Parse("ABCDF456-1234-AABB-3333-AAAACCBBB345")
                        
                    }
                };
            }
			
			//rate param types
            if (_RateParamTypes == null)
            {
                _RateParamTypes = new List<Entities.RateParamType>()
                {
                    new Entities.RateParamType()
                    {
                        TypeId = Guid.Parse("ABCDF456-1234-1111-2222-AAAACCBBBBBB"),
                        Name = "name 01"
                    },
                    new Entities.RateParamType()
                    {
                        TypeId = Guid.Parse("ABCDF456-1234-3333-4444-AAAACCBBBBBB"),
                        Name = "name 02"
                    }
                };
            }
			
			//rates
            if (_Rates == null)
            {
                _Rates = new List<Entities.Rate>()
                {
                    new Entities.Rate()
                    {
                        RateId = Guid.Parse("98765432-1234-AABB-AAFF-AAAACCBBBBBB"),
                        UpdateDate = new DateTime(1980, 5, 10),
                        CountryId = Guid.Parse("98765432-1234-1111-AAFF-AAAACCBBBBBB")
                    },
                    new Entities.Rate()
                    {
                        RateId = Guid.Parse("98765432-10FD-AABB-AAFF-AAAACCBBBBBB"),
                        UpdateDate = new DateTime(1979, 7, 2),
                        CountryId = Guid.Parse("98765432-1234-2222-AAFF-AAAACCBBBBBB")
                    }
                };
            }
			
			//retail rates
            if (_RetailRates == null)
            {
                _RetailRates = new List<Entities.RetailRate>()
                {
                    new Entities.RetailRate()
                    {
                        RetailRateId = Guid.Parse("ABCDF456-1234-5678-90AB-AAAACCBBBBBB"),
                        UpdateDate = new DateTime(1980, 5, 10),
                        BranchId = Guid.Parse("ABCDF456-1234-5678-90AB-AAAACCBBBBB9"),
                        RateId = Guid.Parse("ABCDF456-1234-5678-90AB-AAAACCBBBB19")
                    },
                    new Entities.RetailRate()
                    {
                        RetailRateId = Guid.Parse("ABCDF456-1234-5678-90CC-AAAACCBBBBBB"),
                        UpdateDate = new DateTime(1979, 7, 2),
                        BranchId = Guid.Parse("ABCDF456-1234-5678-90AB-AAAACCBBBBB0"),
                        RateId = Guid.Parse("ABCDF456-1234-5678-90AB-AAAACCBBBB29")
                    }
                };
            }

            //users
            if (_Users == null)
            {
                _Users = new List<Entities.User>()
                {
                    new Entities.Customer()
                    {
                        UserId = Guid.Parse("ABCDF456-1234-5678-90AB-AAAACCBBBB12"),
                    },
                    new Entities.Customer()
                    {
                        UserId = Guid.Parse("ABCDF456-1234-5678-90CC-AAAACCBBBB13"),
                    }
                };
            }

            //bank account types
            if (_BankAccountTypes == null)
            {
                _BankAccountTypes = new List<Entities.BankAccountType>()
                {
                    new Entities.BankAccountType()
                    {
                        TypeId = Guid.Parse("ABCDF456-1234-5678-90CC-22AACCBBBB13"),
                        Name = "Bank Account Type 01"
                    },
                    new Entities.BankAccountType()
                    {
                        TypeId = Guid.Parse("ABCDF456-1234-5678-90CC-33AACCBBBB13"),
                        Name = "Bank Account Type 02"
                    }
                };
            }

            //banks
            if (_Banks == null)
            {
                _Banks = new List<Entities.Bank>()
                {
                    new Entities.Bank()
                    {
                        BankId = Guid.Parse("ABCDF456-4321-5678-90CC-22AACCBBBB13"),
                        Name = "Citi"
                    },
                    new Entities.Bank()
                    {
                        BankId = Guid.Parse("ABCDF456-4321-6678-90CC-33AACCBBBB13"),
                        Name = "Santander Rio"
                    }
                };
            }
        }

        private void InitiateFakeData()
        {
            //
            // Configure object sets for queries
            //

            //address
            this.AddressesGet = () => CreateEntityObjectSet(_Addresses);
            this.CreateSet<Entities.Address>(() => CreateEntityObjectSet(_Addresses));

            //address type
            this.AddressTypesGet = () => CreateEntityObjectSet(_AddressTypes);
            this.CreateSet<Entities.AddressType>(() => CreateEntityObjectSet(_AddressTypes));

            //bank account
            this.BankAccountsGet = () => CreateEntityObjectSet(_BankAccounts);
            this.CreateSet<Entities.BankAccount>(() => CreateEntityObjectSet(_BankAccounts));

            //branch
            this.BranchesGet = () => CreateEntityObjectSet(_Branches);
            this.CreateSet<Entities.Branch>(() => CreateEntityObjectSet(_Branches));

            //cities
            this.CitiesGet = () => CreateEntityObjectSet(_Cities);
            this.CreateSet<Entities.City>(() => CreateEntityObjectSet(_Cities));

            //genders
            this.GendersGet = () => CreateEntityObjectSet(_Genders);
            this.CreateSet<Entities.Gender>(() => CreateEntityObjectSet(_Genders));

            //marital statuses
            this.MaritalStatusesGet = () => CreateEntityObjectSet(_MaritalStatuses);
            this.CreateSet<Entities.MaritalStatus>(() => CreateEntityObjectSet(_MaritalStatuses));

            //countries
            this.CountriesGet = () => CreateEntityObjectSet(_Countries);
            this.CreateSet<Entities.Country>(() => CreateEntityObjectSet(_Countries));

            //group branches
            this.GroupBranchesGet = () => CreateEntityObjectSet(_GroupBranches);
            this.CreateSet<Entities.GroupBranch>(() => CreateEntityObjectSet(_GroupBranches));

            //billing informations
            this.BillingInformationsGet = () => CreateEntityObjectSet(_BillingInformations);
            this.CreateSet<Entities.BillingInformation>(() => CreateEntityObjectSet(_BillingInformations));

            //identity values
            this.IdentitiesGet = () => CreateEntityObjectSet(_Identities);
            this.CreateSet<Entities.Identity>(() => CreateEntityObjectSet(_Identities));

            //identity types
            this.IdentityTypesGet = () => CreateEntityObjectSet(_IdentityTypes);
            this.CreateSet<Entities.IdentityType>(() => CreateEntityObjectSet(_IdentityTypes));

            //orders
            this.OrdersGet = () => CreateEntityObjectSet(_Orders);
            this.CreateSet<Entities.Order>(() => CreateEntityObjectSet(_Orders));

            //phones
            this.PhonesGet = () => CreateEntityObjectSet(_Phones);
            this.CreateSet<Entities.Phone>(() => CreateEntityObjectSet(_Phones));

            //phone types
            this.PhoneTypesGet = () => CreateEntityObjectSet(_PhoneTypes);
            this.CreateSet<Entities.PhoneType>(() => CreateEntityObjectSet(_PhoneTypes));

            //soundex codes
            this.SoundexCodesGet = () => CreateEntityObjectSet(_SoundexCodes);
            this.CreateSet<Entities.SoundexCode>(() => CreateEntityObjectSet(_SoundexCodes));

            //states
            this.StatesGet = () => CreateEntityObjectSet(_States);
            this.CreateSet<Entities.State>(() => CreateEntityObjectSet(_States));

            //credit cards
            this.CreditCardsGet = () => CreateEntityObjectSet(_CreditCards);
            this.CreateSet<Entities.CreditCard>(() => CreateEntityObjectSet(_CreditCards));

            //customer services
            this.CustomerServicesGet = () => CreateEntityObjectSet(_CustomerServices);
            this.CreateSet<Entities.CustomerService>(() => CreateEntityObjectSet(_CustomerServices));

			//group branch currency
            this.GroupBranchCurrenciesGet = () => CreateEntityObjectSet(_GroupBranchCurrencies);
            this.CreateSet<Entities.GroupBranchCurrency>(() => CreateEntityObjectSet(_GroupBranchCurrencies));

			//order details
            this.OrderDetailsGet = () => CreateEntityObjectSet(_OrderDetails);
            this.CreateSet<Entities.OrderDetail>(() => CreateEntityObjectSet(_OrderDetails));

			//rate param types
            this.RateParamTypesGet = () => CreateEntityObjectSet(_RateParamTypes);
            this.CreateSet<Entities.RateParamType>(() => CreateEntityObjectSet(_RateParamTypes));

			//rates
            this.RatesGet = () => CreateEntityObjectSet(_Rates);
            this.CreateSet<Entities.Rate>(() => CreateEntityObjectSet(_Rates));
			
			//retail rates
            this.RetailRatesGet = () => CreateEntityObjectSet(_RetailRates);
            this.CreateSet<Entities.RetailRate>(() => CreateEntityObjectSet(_RetailRates));

            //virtual accounts
            this.VirtualAccountsGet = () => CreateEntityObjectSet(_VirtualAccounts);
            this.CreateSet<Entities.VirtualAccount>(() => CreateEntityObjectSet(_VirtualAccounts));

            //users
            this.UsersGet = () => CreateEntityObjectSet(_Users);
            this.CreateSet<Entities.User>(() => CreateEntityObjectSet(_Users));

            //bank accounts
            this.BankAccountTypesGet = () => CreateEntityObjectSet(_BankAccountTypes);
            this.CreateSet<Entities.BankAccountType>(() => CreateEntityObjectSet(_BankAccountTypes));

            //banks
            this.BanksGet = () => CreateEntityObjectSet(_Banks);
            this.CreateSet<Entities.Bank>(() => CreateEntityObjectSet(_Banks));

            //
            // Configure appply changes
            //

            //address
            this.RegisterChangesTEntity<Entities.Address>(RegisterEntityChanges(_Addresses));

            //address type
            this.RegisterChangesTEntity<Entities.AddressType>(RegisterEntityChanges(_AddressTypes));

            //bank account
            this.RegisterChangesTEntity<Entities.BankAccount>(RegisterEntityChanges(_BankAccounts));

            //bank account
            this.RegisterChangesTEntity<Entities.Branch>(RegisterEntityChanges(_Branches));

            //cities
            this.RegisterChangesTEntity<Entities.City>(RegisterEntityChanges(_Cities));

            //genders
            this.RegisterChangesTEntity<Entities.Gender>(RegisterEntityChanges(_Genders));

            //marital status
            this.RegisterChangesTEntity<Entities.MaritalStatus>(RegisterEntityChanges(_MaritalStatuses));

            //marital status
            this.RegisterChangesTEntity<Entities.Country>(RegisterEntityChanges(_Countries));

            //group branches
            this.RegisterChangesTEntity<Entities.GroupBranch>(RegisterEntityChanges(_GroupBranches));

            //billing informations
            this.RegisterChangesTEntity<Entities.BillingInformation>(RegisterEntityChanges(_BillingInformations));

            //identities
            this.RegisterChangesTEntity<Entities.Identity>(RegisterEntityChanges(_Identities));

            //identity types
            this.RegisterChangesTEntity<Entities.IdentityType>(RegisterEntityChanges(_IdentityTypes));

            //orders
            this.RegisterChangesTEntity<Entities.Order>(RegisterEntityChanges(_Orders));

            //phones
            this.RegisterChangesTEntity<Entities.Phone>(RegisterEntityChanges(_Phones));

            //phone types
            this.RegisterChangesTEntity<Entities.PhoneType>(RegisterEntityChanges(_PhoneTypes));

            //soundex codes
            this.RegisterChangesTEntity<Entities.SoundexCode>(RegisterEntityChanges(_SoundexCodes));

            //states
            this.RegisterChangesTEntity<Entities.State>(RegisterEntityChanges(_States));

            //credit cards
            this.RegisterChangesTEntity<Entities.CreditCard>(RegisterEntityChanges(_CreditCards));

            //customer services
            this.RegisterChangesTEntity<Entities.CustomerService>(RegisterEntityChanges(_CustomerServices));

            //group branch currencies
            this.RegisterChangesTEntity<Entities.GroupBranchCurrency>(RegisterEntityChanges(_GroupBranchCurrencies));

            //order details
            this.RegisterChangesTEntity<Entities.OrderDetail>(RegisterEntityChanges(_OrderDetails));

            //rate param types
            this.RegisterChangesTEntity<Entities.RateParamType>(RegisterEntityChanges(_RateParamTypes));

            //rates
            this.RegisterChangesTEntity<Entities.Rate>(RegisterEntityChanges(_Rates));

            //retail rates
            this.RegisterChangesTEntity<Entities.RetailRate>(RegisterEntityChanges(_RetailRates));
			
            //virtual accounts
            this.RegisterChangesTEntity<Entities.VirtualAccount>(RegisterEntityChanges(_VirtualAccounts));

            //users
            this.RegisterChangesTEntity<Entities.User>(RegisterEntityChanges(_Users));

            //bank account types
            this.RegisterChangesTEntity<Entities.BankAccountType>(RegisterEntityChanges(_BankAccountTypes));

            //banks
            this.RegisterChangesTEntity<Entities.Bank>(RegisterEntityChanges(_Banks));

            //
            //  Set commit stub
            //
            this.Commit = () => { };
            this.CommitAndRefreshChanges = () => { };
        }

        private static MolesDelegates.Action<T> RegisterEntityChanges<T>(List<T> list)
        {
            return t
                                                            =>
            {
                if (t != null
                    &&
                    list != null)
                {
                    int index = list.IndexOf(t);
                    if (index != -1)
					{
                        list[index] = t;
					}
                    else
					{
                        list.Add(t);
					}
                }
            };
        }

        IObjectSet<T> CreateEntityObjectSet<T>(List<T> list) where T : class
        {
            return list.ToMemorySet();
        }

        #endregion
    }
}
